package com.ferdict;

import java.io.BufferedInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.URL;
import java.net.URLConnection;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.List;

import org.apache.http.NameValuePair;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.message.BasicNameValuePair;
import org.json.JSONArray;
import org.json.JSONObject;

import android.app.Activity;
import android.app.AlertDialog;
import android.content.DialogInterface;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Color;
import android.os.Bundle;
import android.util.Log;
import android.view.Gravity;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.TextView;
import android.widget.Toast;

public class FerdictActivity extends Activity implements OnClickListener {
	private static final String tag = "FerdictActivity";
	private static final int LOGIN_REQ_ID = 0;
	private static final int LOGIN_REQ_ID_TO_UPLOAD = 1;
	private static final int LOGIN_REQ_ID_TO_SHARE = 2;
	private static final int SHARE_REQ_ID = 3;

	private String authToken;
	private Outfit currentOutfit;
	private long outfitId;
	private int curOutfitIdIndex;
	private List<Outfit> outfitList;

	void getOutfits() {
		try {
			String jsonList = RestClient.doGet(Constants.SERVER,
					Constants.PORT, Constants.OUTFITS_URL);
			Log.w(tag, "JSON STR = " + jsonList);
			JSONArray outfitsArray = new JSONArray(jsonList);
			outfitList = new ArrayList<Outfit>();
			for (int i = 0; i < outfitsArray.length(); i++) {
				JSONObject o = outfitsArray.getJSONObject(i);
				Outfit outfit = new Outfit.Builder().outfitId(o.getLong("id"))
						.name(o.getString("name")).photo(o.getString("photo"))
						.numLikes(o.getInt("likes"))
						.numDislikes(o.getInt("dislikes"))
						.owner(o.getLong("owner")).share(o.getBoolean("share"))
						.build();
				outfitList.add(outfit);

				if (0 == i) {
					currentOutfit = outfit;
					curOutfitIdIndex = 0;
				}
			}
		} catch (Exception e) {
			Log.e(tag, "Could not get a list of outfits!", e);
		}
	}

	@Override
	public void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.ferdict);

		View v = null;
		if (null != (v = findViewById(R.id.ferdict_login_button_id)))
			v.setOnClickListener(this);
		if (null != (v = findViewById(R.id.ferdict_refresh_button_id)))
			v.setOnClickListener(this);
		if (null != (v = findViewById(R.id.ferdict_logout_button_id)))
			v.setOnClickListener(this);

		if (null != (v = findViewById(R.id.upload_button_id)))
			v.setOnClickListener(this);
		if (null != (v = findViewById(R.id.share_button_id)))
			v.setOnClickListener(this);
		if (null != (v = findViewById(R.id.dislike_button_id)))
			v.setOnClickListener(this);
		if (null != (v = findViewById(R.id.comment_button_id)))
			v.setOnClickListener(this);
		if (null != (v = findViewById(R.id.list_messages_button_id)))
			v.setOnClickListener(this);
		if (null != (v = findViewById(R.id.like_button_id)))
			v.setOnClickListener(this);

		if (null != (v = findViewById(R.id.prev_button_id)))
			v.setOnClickListener(this);
		if (null != (v = findViewById(R.id.next_button_id)))
			v.setOnClickListener(this);
		if (null != (v = findViewById(R.id.list_messages_button_id)))
			v.setOnClickListener(this);

		Log.i(tag, "# v.id.dislikes = "
				+ findViewById(R.id.text_view_id_dislikes));
		Log.i(tag, "# v.id.likes = " + findViewById(R.id.text_view_id_likes));
		getOutfits();
		updatePhoto();
		updateCounts();

		// Intent i = new Intent();
		// i.setClass(FerdictActivity.this, LoginActivity.class);
		// startActivity(i);
		// Context mContext = getApplicationContext();
		// Dialog dialog = new Dialog(mContext);
		//
		// dialog.setContentView(R.layout.login);
		// dialog.setTitle("Custom Dialog");
		//
		// dialog.show();
	}

	private Bitmap getImageBitmap(String url) {
		Bitmap bm = null;
		try {
			URL aURL = new URL(url);
			URLConnection conn = aURL.openConnection();
			conn.connect();
			InputStream is = conn.getInputStream();
			BufferedInputStream bis = new BufferedInputStream(is);
			bm = BitmapFactory.decodeStream(bis);
			bis.close();
			is.close();
		} catch (IOException e) {
			Log.e(tag, "Error getting bitmap", e);
		}
		return bm;
	}

	public void onActivityResult(int requestCode, int resultCode, Intent data) {
		super.onActivityResult(requestCode, resultCode, data);
		if (data != null) {

			if (requestCode == LOGIN_REQ_ID_TO_UPLOAD) {
				authToken = data.getStringExtra("token");
				launchUpload();
			} else if (requestCode == LOGIN_REQ_ID_TO_SHARE) {
				authToken = data.getStringExtra("token");
				launchShare();
			} else if (requestCode == SHARE_REQ_ID) {
				if (data.getIntExtra("numOutfitsShared", 0) > 0) {
					refresh();
				}
			} else if (requestCode == LOGIN_REQ_ID) {
				authToken = data.getStringExtra("token");
				Toast.makeText(this, "You have logged in.", Toast.LENGTH_SHORT)
						.show();
			}
		}
	}

	void refresh() {
		getOutfits();
		updatePhoto();
		updateCounts();
	}

	void launchUpload() {
		Intent i = new Intent(this, UploadActivity.class);
		i.putExtra("token", authToken);
		startActivity(i);
	}

	void launchShare() {
		Intent i = new Intent(this, ShareActivity.class);
		i.putExtra("token", authToken);
		startActivityForResult(i, SHARE_REQ_ID);
	}

	// @Override
	public void onClick(View v) {
		Intent i = null;
		Toast t = null;

		switch (v.getId()) {
		case R.id.ferdict_login_button_id:
			if (null == authToken) {
				startActivityForResult((new Intent(this, LoginActivity.class)),
						LOGIN_REQ_ID);
			} else {
				Toast.makeText(this,
						"Already logged in as '" + authToken + "'.",
						Toast.LENGTH_SHORT).show();
			}
			break;
		case R.id.ferdict_logout_button_id:
			if (null == authToken || 0 == authToken.length()) {
				Toast.makeText(
						this,
						String.format("You are not logged in.",
								currentOutfit.getName()), Toast.LENGTH_SHORT)
						.show();
				break;
			}

			DialogInterface.OnClickListener dialogClickListener = new DialogInterface.OnClickListener() {
				public void onClick(DialogInterface dialog, int which) {
					switch (which) {
					case DialogInterface.BUTTON_POSITIVE:
						try {
							if (RestClient.doPut(Constants.SERVER,
									Constants.PORT, Constants.LOGIN_URL
											+ "?token=" + authToken, "")) {

								Toast.makeText(FerdictActivity.this,
										"You have logged off.",
										Toast.LENGTH_SHORT).show();
								authToken = null;
							}
						} catch (Exception e1) {
							Log.e(tag, "Could not log off.", e1);
							Toast t = Toast.makeText(FerdictActivity.this,
									"You have logged off.", Toast.LENGTH_SHORT);
							t.getView().setBackgroundColor(Color.RED);
							t.show();
						}
						break;

					case DialogInterface.BUTTON_NEGATIVE:
						break;
					}
				}
			};

			AlertDialog.Builder builder = new AlertDialog.Builder(this);
			builder.setMessage("Are you sure you want to log off?")
					.setPositiveButton("Yes", dialogClickListener)
					.setNegativeButton("No", dialogClickListener).show();

			break;
		case R.id.ferdict_refresh_button_id:
			refresh();
			break;
		case R.id.upload_button_id:
			if (null == authToken) {
				startActivityForResult((new Intent(this, LoginActivity.class)),
						LOGIN_REQ_ID_TO_UPLOAD);
			} else {
				launchUpload();
			}
			break;
		case R.id.share_button_id:
			if (null == authToken) {
				startActivityForResult((new Intent(this, LoginActivity.class)),
						LOGIN_REQ_ID_TO_SHARE);
			} else {
				launchShare();
			}
			break;

		case R.id.like_button_id:
			t = Toast.makeText(this, String.format(
					"Could not update Outfit(id='%d')!", outfitId),
					Toast.LENGTH_SHORT);
			t.getView().setBackgroundColor(Color.RED);
			try {

				if (RestClient.doPut(
						Constants.SERVER,
						Constants.PORT,
						Constants.OUTFITS_URL + "?id="
								+ currentOutfit.getOutfitId() + "&like=1", "")) {

					t = Toast.makeText(this, String.format(
							"Outfit(name='%s') APPROVED.",
							currentOutfit.getName()), Toast.LENGTH_SHORT);
					// t.getView().setBackgroundColor(Color.GREEN);

					currentOutfit.setNumLikes(currentOutfit.getNumLikes() + 1);
					updateCounts();
				}
			} catch (Exception e) {
				Log.e(tag, String.format("Could not update Outfit(id='%d')!",
						currentOutfit.getOutfitId()), e);
			}

			t.setGravity(Gravity.CENTER_VERTICAL, 0, 0);
			t.show();

			break;

		case R.id.dislike_button_id:
			t = Toast.makeText(this, String.format(
					"Could not update Outfit(id='%d')!", outfitId),
					Toast.LENGTH_SHORT);
			t.getView().setBackgroundColor(Color.RED);
			try {

				if (RestClient.doPut(
						Constants.SERVER,
						Constants.PORT,
						Constants.OUTFITS_URL + "?id="
								+ currentOutfit.getOutfitId() + "&like=0", "")) {

					t = Toast.makeText(this, String.format(
							"Outfit(name='%s') DISAPPROVED.",
							currentOutfit.getName()), Toast.LENGTH_SHORT);
					// t.getView().setBackgroundColor(Color.GREEN);

					currentOutfit
							.setNumDislikes(currentOutfit.getNumDislikes() + 1);
					updateCounts();
				}
			} catch (Exception e) {
				Log.e(tag, String.format("Could not update Outfit(id='%d')!",
						outfitId), e);
			}

			t.setGravity(Gravity.CENTER_VERTICAL, 0, 0);
			t.show();
			break;

		case R.id.comment_button_id:
			String cmt = ((EditText) findViewById(R.id.comment_text_area))
					.getText().toString();
			if (null == cmt || cmt.length() == 0) {
				Toast.makeText(this, "Comment cannot be empty.",
						Toast.LENGTH_SHORT).show();
				break;
			}

			t = Toast.makeText(this, String.format(
					"Could not add comment for Outfit(name='%s')!",
					currentOutfit.getName()), Toast.LENGTH_SHORT);
			t.getView().setBackgroundColor(Color.RED);
			try {
				ArrayList<NameValuePair> nameValuePairs = new ArrayList<NameValuePair>();
				nameValuePairs.add(new BasicNameValuePair("id", ""
						+ currentOutfit.getOutfitId()));
				nameValuePairs
						.add(new BasicNameValuePair(
								"comment",
								URLEncoder
										.encode(((EditText) findViewById(R.id.comment_text_area))
												.getText().toString(), "utf-8")));
				if (null != RestClient.doPost(Constants.SERVER, Constants.PORT,
						Constants.COMMENTS_URL, new UrlEncodedFormEntity(
								nameValuePairs))) {
					// "?id="
					// + currentOutfit.getOutfitId()
					// + "&comment="
					// + URLEncoder
					// .encode(((EditText) findViewById(R.id.comment_text_area))
					// .toString(), "utf-8"))) {

					t = Toast.makeText(this,
							String.format("Comment added.", outfitId),
							Toast.LENGTH_SHORT);
					((EditText) findViewById(R.id.comment_text_area))
							.setText("");
					// .setHint("New comment");

				}
			} catch (Exception e) {
				Log.e(tag, String.format("Could not update Outfit(id='%d')!",
						outfitId), e);
			}

			t.setGravity(Gravity.CENTER_VERTICAL, 0, 0);
			t.show();
			break;

		case R.id.prev_button_id:
			Log.i(tag, "curIndex = " + curOutfitIdIndex);
			if (curOutfitIdIndex == outfitList.size() - 1) {
				t = Toast.makeText(this, "No older outfits available.",
						Toast.LENGTH_SHORT);
				t.setGravity(Gravity.CENTER_VERTICAL, 0, 0);
				t.show();
				break;
			}
			currentOutfit = outfitList.get(++curOutfitIdIndex);
			updatePhoto();
			updateCounts();
			break;
		case R.id.next_button_id:
			if (curOutfitIdIndex == 0) {
				t = Toast.makeText(this, "No newer outfits available.",
						Toast.LENGTH_SHORT);
				t.setGravity(Gravity.CENTER_VERTICAL, 0, 0);
				t.show();
				break;
			}
			currentOutfit = outfitList.get(--curOutfitIdIndex);
			updatePhoto();
			updateCounts();
			break;
		case R.id.list_messages_button_id:
			i = new Intent(this, CommentsActivity.class);
			i.putExtra("outfitId", currentOutfit.getOutfitId());
			startActivity(i);
			break;
		}

	}

	void updatePhoto() {
		((ImageView) findViewById(R.id.image_view_id_photo))
				.setImageBitmap(getImageBitmap(currentOutfit.getPhotoUrl()));
		((TextView) findViewById(R.id.home_text_view_outfit_name_id))
				.setText(currentOutfit.getName());
	}

	void updateCounts() {
		TextView v = ((TextView) findViewById(R.id.text_view_id_likes));
		v.setText("" + currentOutfit.getNumLikes());

		v = ((TextView) findViewById(R.id.text_view_id_dislikes));
		v.setText("" + currentOutfit.getNumDislikes());
	}

	// private void toast(String s, int duration) {
	// LayoutInflater inflater = getLayoutInflater();
	// View layout = inflater.inflate(R.layout.toast,
	// (ViewGroup) findViewById(R.id.toast_layout_root));
	//
	// TextView text = (TextView) layout.findViewById(R.id.text);
	// text.setText(s);
	//
	// Toast toast = new Toast(getApplicationContext());
	// toast.setGravity(Gravity.CENTER_VERTICAL, 0, 0);
	// toast.setDuration(duration);
	// toast.setView(layout);
	// toast.show();
	// }
}